﻿using System.Linq;
using TMPro;
using UnityEngine;
using UnityEngine.UI;

namespace HEFramework
{
    public static class SummonUISystem
    {
        [EntitySystem]
        public class SummonUIAwakeSystem : AwakeSystem<SummonUI>
        {
            protected override void Awake(SummonUI _self)
            {
                _self.AddChild<UnityObjectComponent>();
            }
        }

        [EntitySystem]
        public class SummonUIUpdateSystem : UpdateSystem<SummonUI>
        {
            protected override void Update(SummonUI _self)
            {
                _self.Update();
            }
        }

        [EntitySystem]
        public class SummonUIDestroySystem : DestroySystem<SummonUI>
        {
            protected override void Destroy(SummonUI _self)
            {
                _self.Close();
            }
        }


        public static void Open(this SummonUI _self)
        {
            var uc = _self.GetScene().GetChild<UIComponent>();
            if (uc == null)
            {
                return;
            }

            uc.PushUIAsync(eUIFlag.Summon, _ =>
            {
                _self.UIWindowBehaviour = _;
                _self.Bind();
                _self.Update(true);
            });
        }

        public static void Bind(this SummonUI _self)
        {
            if (_self.UIWindowBehaviour == null)
            {
                return;
            }

            _self.UIWindowBehaviour.GetButton("Button_Back").RegisterUpEvent(_self.Close);
            _self.UIWindowBehaviour.GetButton("Button_Summon").RegisterUpEvent(_self.Summon);
            _self.UIWindowBehaviour.GetButton("Button_ReSummon").RegisterUpEvent(_self.Summon);
            for (int i = 0; i < 3; i++)
            {
                int index = i;
                _self.UIWindowBehaviour.GetButton($"Button_SummonItem{i}").RegisterUpEvent(() => { _self.Select(index); });
            }
        }

        public static void Update(this SummonUI _self, bool _isNew = false)
        {
            if (_self.UIWindowBehaviour == null || _self.UIWindowBehaviour.State == 0)
            {
                return;
            }

            _self.UpdateSummonButton(_isNew);
            _self.UpdateMenu();
        }

        public static void Close(this SummonUI _self)
        {
            if (_self.UIWindowBehaviour == null)
            {
                return;
            }

            _self.RecyclePrefab();
            _self.UIWindowBehaviour.Hide();
            _self.UIWindowBehaviour = null;
        }

        public static void Summon(this SummonUI _self)
        {
            var summon = _self.GetSceneChild<Summon>();
            if (summon == null)
            {
                return;
            }

            if (summon.Summon())
            {
                _self.Update(true);
            }
        }

        public static void Select(this SummonUI _self, int _index)
        {
            var dc = _self.GetSceneChild<DataTableComponent>();
            if (dc == null)
            {
                return;
            }

            var summon = _self.GetSceneChild<Summon>();
            if (summon == null)
            {
                return;
            }

            if (_index >= summon.Lotteries.Count)
            {
                return;
            }

            int code = summon.Select(summon.Lotteries[_index]);

            switch (code)
            {
                case (int)eSummonErrorCode.None:
                    _self.Update(true);
                    break;
                case (int)eSummonErrorCode.System:
                    break;
                case (int)eSummonErrorCode.OutLimit:
                    var reporterUI = _self.GetSceneChild<ReporterUI>();
                    if (reporterUI != null)
                    {
                        reporterUI.Reporter(dc.LoadDataTable<DRLanguage>().GetData(116).Text);
                    }

                    break;
            }
        }

        private static void UpdateMenu(this SummonUI _self)
        {
            var dc = _self.GetSceneChild<DataTableComponent>();
            var player = _self.GetSceneChild<Player>();
            var summon = _self.GetSceneChild<Summon>();
            var uc = _self.GetChild<UnityObjectComponent>();
            if (dc == null || player == null || summon == null || uc == null)
            {
                return;
            }

            var table = dc.LoadDataTable<DRGlobalSettings>();


            var summonBtn = _self.UIWindowBehaviour.GetButton("Button_Summon");
            var name = summonBtn.GetTransform().GetChild(0);
            var costItem = summonBtn.GetTransform().GetChild(1);
            var costIcon = uc.Get<Image>(costItem.GetChild(0).gameObject);
            var costText = uc.Get<TMP_Text>(costItem.GetChild(1).gameObject);


            string money = table.GetData((int)eGlobalSetting.Summon_Hero_G).Value1.ToString();
            //表示有已招募对象
            if (summon.IsHaveCache())
            {
                //够钱重新招募
                if (player.G >= table.GetData((int)eGlobalSetting.Summon_Hero_G).Value1)
                {
                    summonBtn.Enable(true);
                }
                //没钱
                else
                {
                    summonBtn.Enable(false);
                }
                //高亮特效
            }
            else
            {
                //够钱招募
                if (player.G >= table.GetData((int)eGlobalSetting.Summon_Hero_G).Value1)
                {
                    summonBtn.Enable(true);
                }
                //没钱
                else
                {
                    summonBtn.Enable(false);
                }
            }
        }

        private static void UpdateSummonButton(this SummonUI _self, bool _isNew)
        {
            var dc = _self.GetSceneChild<DataTableComponent>();
            var pc = _self.GetSceneChild<PrefabComponent>();
            var summon = _self.GetSceneChild<Summon>();
            if (dc == null || pc == null || summon == null)
            {
                return;
            }

            var hero_table = dc.LoadDataTable<DRHero>();
            var attribute_table = dc.LoadDataTable<DRAttribute>();
            var introduce_table = dc.LoadDataTable<DRIntroduce>();

            if (_isNew)
            {
                _self.RecyclePrefab();
                string extend = "_Image";
                //按钮处理
                int b_max = 3;
                for (int i = 0; i < b_max; i++)
                {
                    var button = _self.UIWindowBehaviour.GetButton($"Button_SummonItem{i}");
                    var icon = button.GetTransform().GetChild(0);
                    var name = button.GetTransform().GetChild(1);
                    var introduce = button.GetTransform().GetChild(2);

                    bool is_show = true;

                    if (summon.Lotteries.Count == 0)
                    {
                        is_show = false;
                    }
                    else
                    {
                        if (i < summon.Lotteries.Count)
                        {
                            if (summon.Lotteries[i] == -1)
                            {
                                is_show = false;
                            }
                        }
                        else
                        {
                            is_show = false;
                        }
                    }

                    if (is_show)
                    {
                        button.Enable(true);
                        icon.gameObject.SetActive(true);
                        name.gameObject.SetActive(true);
                        introduce.gameObject.SetActive(true);

                        var hData = hero_table.GetData(summon.Lotteries[i]);
                        var aData = attribute_table.GetData(hData.ID);
                        string abName = Formula.CN(aData.ABName, 0) + extend;
                        //异步加载对象
                        pc.GetPrefabAsync(aData.ABPath, abName, _ =>
                        {
                            //加载完成时发现UI关闭，则回收
                            if (_self.UIWindowBehaviour != null && _self.UIWindowBehaviour.State != 1)
                            {
                                pc.Recycle(aData.ABPath, abName, _);
                            }
                            else
                            {
                                _.transform.SetParent(icon, false);
                                _.transform.localPosition = Vector2.zero;
                                var image = new SummonUI.Image();
                                image.ID = aData.ID;
                                image.ABPath = aData.ABPath;
                                image.ABName = aData.ABName;
                                image.Obj = _;
                                _self.HeroImages.Add(image);
                            }
                        });
                        //更新名字
                        name.GetComponent<TMP_Text>().SetText(aData.Name);

                        var titles = introduce_table.GetAllData();
                        //更新介绍
                        for (int j = 0; j < 4; j++)
                        {
                            var introduceItem = introduce.GetChild(j);
                            var title = introduceItem.GetChild(0);
                            var bar = introduceItem.GetChild(1);
                            title.GetComponent<TMP_Text>().SetText(titles[j].Name);

                            int value = hData.Introduces[j];
                            for (int k = 0; k < bar.childCount; k++)
                            {
                                if (k < value)
                                {
                                    bar.GetChild(k).GetChild(0).gameObject.SetActive(false);
                                    bar.GetChild(k).GetChild(1).gameObject.SetActive(true);
                                }
                                else
                                {
                                    bar.GetChild(k).GetChild(0).gameObject.SetActive(true);
                                    bar.GetChild(k).GetChild(1).gameObject.SetActive(false);
                                }
                            }
                        }
                    }
                    else
                    {
                        button.Enable(false);
                        icon.gameObject.SetActive(false);
                        name.gameObject.SetActive(false);
                        introduce.gameObject.SetActive(false);
                    }
                }
            }
        }

        private static void RecyclePrefab(this SummonUI _self)
        {
            var pc = _self.GetSceneChild<PrefabComponent>();

            if (pc == null)
            {
                return;
            }

            string extend = "_Image";

            //表示之前招募过,回收对象
            if (_self.HeroImages.Count > 0)
            {
                for (int i = 0; i < _self.HeroImages.Count; i++)
                {
                    var image = _self.HeroImages[i];
                    pc.Recycle(image.ABPath, Formula.CN(image.ABName, 0) + extend, image.Obj);
                }

                _self.HeroImages.Clear();
            }
        }
    }
}